package com.yuandian.customer.perception.controller;

import com.yuandian.api.customer_perception.po.*;
import com.yuandian.api.customer_perception.vo.AlarmOverviewVo;
import com.yuandian.api.customer_perception.vo.ReturnCodeDetailVo;
import com.yuandian.bpm.common.core.util.R;
import com.yuandian.customer.perception.service.IBusinessAlarmService;
import com.yuandian.utils.PageDataInfo;
import com.yuandian.utils.poi.ExcelTitleUtils;
import com.yuandian.utils.poi.ExcelUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
 * 说明：业务告警controller
 * @Author yanjun
 * @Date 2021/3/30 9:22
 */
@Slf4j
@RestController
@Api(value = "告警分析", tags = "告警分析")
@RequestMapping("/alarm/business")
public class BusinessAlarmController {

    @Autowired
    private IBusinessAlarmService businessAlarmService;

    /**
     * 查询告警类型比例
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping("/queryAlarmTypeProportion")
    @ApiOperation(value = "告警分析-查询告警类型比例", notes = "告警分析-查询告警类型比例")
    public R<Object> queryAlarmTypeProportion(@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryAlarmTypeProportion(params);
    }


    /**
     * 查询告警数topN
     *
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping("/queryAlarmCountTopN")
    @ApiOperation(value = "告警分析-查询告警数topN", notes = "告警分析-查询告警数topN")
    public R<Object> queryAlarmTypeCountTopN(@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryAlarmTypeCountTop(params);
    }


    /**
     * 查询影响区域最多的告警topN
     *
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping(value = "/queryAlarmAreaTopN")
    @ApiOperation(value = "告警分析-查询影响区域最多的告警topN", notes = "告警分析-查询影响区域最多的告警topN")
    public R<Object> queryAlarmAreaTopN (@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryInfluenceAreaTop(params);
    }



    /**
     * 查询影响业务最多的故障top
     *
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping("/queryAlarmBusiTopN")
    @ApiOperation(value = "告警分析-查询影响业务最多的故障top", notes = "告警分析-查询影响业务最多的故障top")
    public R<Object> queryAlarmBusiTopN(@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryInfluenceBusiTop(params);
    }


    /**
     * 查询发生次数最多的故障top
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping("/queryHappenCountAlarmTop")
    @ApiOperation(value = "告警分析-查询发生次数最多的故障top", notes = "告警分析-查询发生次数最多的故障top")
    public R<Object> queryHappenCountAlarmTop(@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryHappenCountAlarmTop(params);
    }

    /**
     * 查询发生故障最多的系统top
     *
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping("/queryAlarmSystemTopN")
    @ApiOperation(value = "告警分析-查询发生故障最多的系统top", notes = "告警分析-查询发生故障最多的系统top")
    public R<Object> queryAlarmSystemTopN(@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryInfluenceSysTop(params);
    }

    /**
     * 查询告警统计列表
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping("/queryAlarmStatisticsList")
    @ApiOperation(value = "告警分析-查询告警统计列表", notes = "告警分析-查询告警统计列表")
    public R<Object> queryAlarmStatisticsList(@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryAlarmStatisticsList(params);
    }

    /**
     * 查询告警详情列表
     * @param params 业务告警请求对象
     * @return 通用返回对象
     */
    @PostMapping("/queryAlarmDetailList")
    @ApiOperation(value = "告警分析-查询告警详情列表", notes = "告警分析-查询告警详情列表")
    public R<PageDataInfo> queryAlarmDetailList(@RequestBody BusinessAlarmParams params) {
        return businessAlarmService.queryAlarmDetailList(params);
    }


    /**
     * 查询系统告警总览
     *
     * @param params 系统告警请求参数
     * @return 通用返回对象
     */
    @PostMapping(value = "/systemAlarmOverview")
    @ApiOperation(value = "告警分析-查询告警详情列表", notes = "告警分析-查询告警详情列表")
    public R<Object> queryAlarmOverviewList (@RequestBody AlarmOverviewParams params) {
        params.handleQueryParam();
        return businessAlarmService.querySystemAlarmOverviewList(params);
    }


    /**
     * 查询系统告警总览 - excel 下载
     *
     * @param params 系统告警请求参数
     * @param response 响应对象
     */
    @PostMapping(value = "/systemAlarmOverviewExcel")
    @ApiOperation(value = "告警分析-查询系统告警总览 - excel 下载", notes = "告警分析-查询系统告警总览 - excel 下载")
    public void queryAlarmOverviewExcel (@RequestBody AlarmOverviewParams params, HttpServletResponse response) throws Exception {
        params.handleQueryParam();

        params.setPageNum(1);
        params.setPageSize(-1);

        // 查询数据
        R<Object> result = businessAlarmService.querySystemAlarmOverviewList(params);
        PageDataInfo pageDataInfo = (PageDataInfo) result.getData();
        List<AlarmOverviewVo> data = new ArrayList<>();
        try {
            data = (List<AlarmOverviewVo>) pageDataInfo.getData();
        } catch (Exception e) {
            log.error("所选时间表不存在!但表格需要正常导出.");
        }
        int index = 1;
        for (AlarmOverviewVo datum : data) {
            datum.setId(index++);
            datum.setSuccessRate(datum.getSuccessRate()+"%");
            datum.setHealthRate(datum.getHealthRate()+"%");
        }
        String title = "业务告警数据总览表";

        String fileName = title + System.currentTimeMillis();

        //设置大标题
        List<String> titleParams = new ArrayList<>();
        titleParams.add(title);
        titleParams.add(params.getSystemName() == null?"全系统":params.getSystemName());
        String formTitleName = ExcelTitleUtils.formTitleName(titleParams,params.getStartTime(),params.getEndTime());

        List<List<String>> headList = new ArrayList<>();
        List<String> titleList = Arrays.asList("序号","系统名称", "业务名称", "访问量", "受理量", "告警访问量", "系统返回码", "业务提示语", "业务返回码", "成功率"
                , "健康度");

        titleList.forEach(s -> {
            List<String> childHeadList = new ArrayList<>();
            childHeadList.add(formTitleName);
            childHeadList.add(s);
            headList.add(childHeadList);
        });

        ExcelUtil.writeExcel(AlarmOverviewVo.class, fileName, title, data, headList, 20, response);
    }


    /**
     * 查询告警周期柱状图
     *
     *
     * @param params 请求参数
     * @return 通用返回对象
     */
    @PostMapping(value = "/histogram")
    @ApiOperation(value = "告警分析-查询告警周期柱状图", notes = "告警分析-查询告警周期柱状图")
    public R<Object> queryHistoGramList (@RequestBody HistoGramParams params) {
        return businessAlarmService.queryHistogramDetail(params);
    }


    /**
     * 查询用户告警列表
     *
     * @param params 用户告警查询请求参数
     * @return 通用返回对象
     */
    @PostMapping(value = "/queryUserAlarmList")
    @ApiOperation(value = "告警分析-查询用户告警列表", notes = "告警分析-查询用户告警列表")
    public R<Object> queryUserAlarmList (@RequestBody UserIdentifyAlarmParams params) {
        return businessAlarmService.queryUserAlarmList(params);
    }


    /**
     * 查询告警分布
     *
     * @param params 请求参数
     * @return 通用返回对象
     */
    @PostMapping(value = "/queryAlarmDistribution")
    @ApiOperation(value = "告警分析-查询告警分布", notes = "告警分析-查询告警分布")
    public R<Object> queryAlarmDistribution (@RequestBody AlarmDistributionParams params) {
        return businessAlarmService.queryAlarmDistribution(params);
    }


    /**
     * 查询告警详情
     *
     * @param params 请求参数
     * @return 通用返回对象
     */
    @PostMapping(value = "/queryReturnCodeDetailList")
    @ApiOperation(value = "告警分析-查询告警详情", notes = "告警分析-查询告警详情")
    public R<Object> queryReturnCodeDetailList (@RequestBody AlarmDistributionParams params) {
        return businessAlarmService.queryReturnCodeDetail(params);
    }

    /**
     * 查询告警详情 -- 下载
     *
     * @param params 请求参数
     * @param response 响应对象
     */
    @PostMapping(value = "/queryReturnCodeDetailListExcel")
    @ApiOperation(value = "告警分析-查询告警详情 -- 下载", notes = "告警分析-查询告警详情 -- 下载")
    public void queryReturnCodeDetailListExcel (@RequestBody AlarmDistributionParams params, HttpServletResponse response) throws Exception {
        params.setPageNum(1);
        params.setPageSize(10000000L);

        R<Object> result = businessAlarmService.queryReturnCodeDetail(params);
        PageDataInfo pageDataInfo = (PageDataInfo) result.getData();
        List<ReturnCodeDetailVo> data = (List<ReturnCodeDetailVo>) pageDataInfo.getData();
        data.forEach(item -> item.handleAlarmName());
        int index = 1;
        for (ReturnCodeDetailVo datum : data) {
            datum.setId(index++);
        }

//        String titleFormat = "%s告警业务详情表 ";
        String title = "告警详情表";
        String fileName = title + System.currentTimeMillis();
        List<String> titleParams = new ArrayList<>();
        titleParams.add(title);
        titleParams.add(params.getSystemName());
        titleParams.add(params.getBusinessName());
        titleParams.add(params.getReturnCode());
        String formTitleName = ExcelTitleUtils.formTitleName(titleParams,params.getStartTime(),params.getEndTime());

        List<List<String>> headList = new ArrayList<>();
        List<String> titleList = Arrays.asList("序号", "系统名称", "业务名称", "告警级别", "服务器返回码", "发生时间", "告警描述");

        titleList.forEach(s -> {
            List<String> childHeadList = new ArrayList<>();
            childHeadList.add(formTitleName);
            childHeadList.add(s);
            headList.add(childHeadList);
        });

        ExcelUtil.writeExcel(ReturnCodeDetailVo.class, fileName, "告警业务详情", data, headList,30,  response);
    }


    /**
     * 查询告警级别列表
     *
     * @return 通用返回对象
     */
    @PostMapping(value = "queryAlarmLevelList")
    @ApiOperation(value = "告警分析-查询告警级别列表", notes = "告警分析-查询告警级别列表")
    public R<Object> queryAlarmLevelList () {
        return businessAlarmService.queryAlarmLevelList();
    }

    /**
     * 系统业务告警列表
     * @param params
     * @return
     */
    @PostMapping(value = "alarmSysAndBusiList")
    @ApiOperation(value = "告警分析-系统业务告警列表", notes = "告警分析-系统业务告警列表")
    public R<Object> alarmSysAndBusiList(@RequestBody AlarmSysAndBusiParams params){
        return businessAlarmService.alarmSysAndBusiList(params);
    }

    /**
     * 系统业务告警列表导出
     * @param params
     * @return
     */
    @PostMapping(value = "alarmSysAndBusiListExport")
    @ApiOperation(value = "告警分析-系统业务告警列表导出", notes = "告警分析-系统业务告警列表导出")
    public void alarmSysAndBusiListExport(@RequestBody AlarmSysAndBusiParams params, HttpServletResponse response) {
        try {
            businessAlarmService.alarmSysAndBusiListExport(params, response);
        } catch (IOException e) {
            e.printStackTrace();
//            ResponseUtil.setResponseResult(Result.setFail(-1, e.getMessage()), response);
        }
    }

    /**
     * 告警实值统计列表
     * @param params
     * @return
     */
    @PostMapping(value = "alarmOverviewList")
    @ApiOperation(value = "告警分析-告警实值统计列表", notes = "告警分析-告警实值统计列表")
    public R<Object> alarmOverviewList(@RequestBody AlarmSysAndBusiParams params){
        return businessAlarmService.alarmOverviewList(params);
    }

    /**
     * 系统业务告警列表导出
     * @param params
     * @return
     */
    @PostMapping(value = "alarmOverviewListExport")
    @ApiOperation(value = "告警分析-系统业务告警列表导出", notes = "告警分析-系统业务告警列表导出")
    public void alarmOverviewListExport(@RequestBody AlarmSysAndBusiParams params, HttpServletResponse response) throws ParseException, IOException {
        try {
            businessAlarmService.alarmOverviewListExport(params, response);
        } catch (IOException e) {
            e.printStackTrace();
//            ResponseUtil.setResponseResult(Result.setFail(-1, e.getMessage()), response);
        }
    }
}
